home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Amiga Collections: Various
/
DevDisk 65 (1989)(DevWare PD).zip
/
DevDisk 65 (1989)(DevWare PD).adf
/
mypixel
/
pixel.asm
< prev
next >
Wrap
Assembly Source File
|
1990-07-11
|
6KB
|
145 lines
; Routine to draw one pixel at desired location.
; After the pedantic Geodesic Publications code, Linesdemo.
; C call is pixel ( &bitmap, color number, x, y );
; Bitmap pointer passed on stack to facilitate dual-playfield calls.
; Compiler = Manx 3.6A
; Thomas J. Eshelman Reading, Pa. 12/20/88
CSEG
public _pixel
DSEG
bm_BytesPerRow equ 0
bm_Depth equ 5
bm_Planes equ 8
CSEG
_pixel:
movem.l d2-d7/a2-a6,-(sp) Save non-scratch registers.
;At this point, we have 44 bytes for the 11 registers and 4 bytes the
;system used to save the return address when we called _pixel between
;us and the arguments we passed and want to retrieve from the stack.
;Hence, the first argument is located 48 bytes above the bottom.
;This is because the stack decreases as it gets larger. (It was invented
;by an Congressional Committee, you see.) The LAST argument saved to the
;stack is the FIRST one available to come off. Hence, the first one to
;come off, the one with the lowest address, is the bitmap pointer.
move.l 48(a7),a5 Pointer to desired bitmap.
movem.w 52(a7),d0-d2 MOVEM pops args in SAME order pushed.
move.w d0,d3 Copy color value for the helluva it.
move.w d2,d7 Copy Y coordinate.
mulu bm_BytesPerRow(a5),d7 Byte offset of line containing Y.
;d7 now holds the offset value, in number of bytes from the beginning of
;each display plane, of the first byte of the line in which we find the
;'Y' coordinate. All we need do now is find out how far to the right, on
;this line, of course, we must move in order to locate 'X' coordinate.
move.w d1,d4 Copy X coordinate.
;The next 2 instructs divide X by 8 in order to convert BITS (the coord.
;being expressed in terms of bits) into BYTES. We have the second step
;to guarantee an even result. (Shifting is much faster than division).
lsr.w #4,d4
lsl.w #1,d4
;The resulting base offset from the beginning of a line is added to the
;the Y offset so we now have the offset of the byte in the plane that
;we want to use to draw the pixel. From here on, we must advance bit
;by bit (yuk, yuk, yuk!).
add.w d4,d7
ext.l d7
move.w d1,d4 Recopy X coordinate.
;This simple move yields how many BITS further right we must advance
;prior to drawing the pixel. Consider an X value of 150. This is binary
;1001 0110. Divided by 8 is 18 with 6 left over. So we will move left
;18 bytes followed by 6 bits to draw. The number of those bits we must
;advance is necessarily contained in the rightmost nybble. Please extract.
andi.w #$f,d4 Thank you.
;Set a bit in the high order byte of a register word that will represent
;the bit to be moved right, if at all. This bit represents the pixel we
;will draw or erase. Obviously, we then shift this bit into the exact
;position we determined by the algorithm above. (In the above example,
;this would be 6 bits right, which yields a literal hex value of $0200.
;Don't worry about 'value'. That is for illustration only. We are only
;concerned with the physical bit position.)
move.w #$8000,d5
lsr.w d4,d5
move.w d5,d6 d5 has the OR mask for pixel draw.
;0000 0010 0000 0000
not.w d6 Prepare an AND mask for pixel erase.
;1111 1101 1111 1111
move.b bm_Depth(a5),d0 Number of planes to draw into.
ext.w d0
subq.w #1,d0 Subtract one from Depth for dbra.
clr.w d1 Actual Depth or Plane counter.
10$:
;Multiply the counter by 4 and add it to the PLANEPTR value so that it
;points to the next plane. (0, 4, 8, 12, 16 byte offsets). bm_Planes is
;but an Array of Pointers, each pointing the to base of the next plane
;comprising our bitmap.
move.w d1,d2
lsl.w #2,d2 Plane number times 4.
movea.l bm_Planes(a5,d2),a3 Retrieve this PLANEPTR.
add.l d7,a3 Come to byte in which we shall plant
; our pixel.
;Achtung! For the user's color choice, see to it that the bits for each
;plane are set or reset so that the pixel of this color are in fact
;displayed. For example, if the user asked for color 5, then to draw a
;pixel in that color in plane 1, we must be sure to zero the bit.
btst d1,d3 Test the color bit in our plane.
beq 20$ Branch if unset.
;a3 points to the byte containing the coordinate. However, we will OR a
;WORD against this BYTE. Observe, supra, it is the HIGH order BYTE of d5
;and d6 that contain the 'shift mask' (which in our example is $0200.
;That makes the high order byte of said word, $02).
;Observe, also, that with the 68000, the high byte of the register is the
;lower address in memory. Therefore, we are applying the mask to the
;exact BYTE referenced by (a3) and to the byte above that, (which latter
;is of no effect because it always gets ORed with zeros).
or.w d5,(a3) Set the coordinate bit. Behold!!
bra 30$ Test next plane.
20$:
and.w d6,(a3) Reset the coordinate bit. Zap!
30$:
addq.w #1,d1 Advance to next plane, and to the
dbra d0,10$ corresponding binary color bit.
movem.l (sp)+,d2-d7/a2-a6 Pop user stack.
rts
end